"""
可以内置到排期软件，
也可以作为一个独立的软件
"""
import os
import sys
import time
import threading
from functools import wraps
from PyQt5.QtGui import *
from PyQt5.QtWidgets import  *
from PyQt5.QtCore import *
from PyQt5.QtWebEngineWidgets import *
from PyQt5.QtWebChannel import *
from calendarWindow import Calendar
from pyecharts import options as opts
from pyecharts.charts import Sankey,Pie,Liquid
from pyecharts.commons.utils import JsCode
from db_handler import DB_handler
from mz_date import MZ_Date
from project_hot import ProjectHotWindow
from department_statistical_window import DepartmentStatisticalWindow

def info(arg):   #修饰函数
    def _info(func):
        @wraps(func)
        def wrapper(*args,**kwargs):

            if arg=='len':
                ret = func(*args, **kwargs)#
                if ret:
                    c=len(ret[0])
                    print('等分长度:{} 拆分后列表长度:{}'.format(c,len(ret)))
                else:
                    print('拆分列表为空')
            elif arg=='time':
                start=time.time()
                ret = func(*args, **kwargs)#, **kwargs
                end=time.time()
                print('运行时间:{}'.format(end-start))
            return ret
        return wrapper
    return _info

class TInteractObj(QObject):
    SigReceivedMessFromJS = pyqtSignal(str)
    SigSendMessageToJS = pyqtSignal(str)

    def __init__(self, parent=None):
        super().__init__(parent)

    @pyqtSlot(str)
    def JSSendMessage(self, strParameter):
        print('JSSendMessage(%s) from Html' % strParameter)
        self.SigReceivedMessFromJS.emit(strParameter)

    @pyqtSlot(result=str)
    def fun(self):
        print('TInteractObj.fun()')
        return 'hello'


class ManPower(QWidget):

    def __init__(self):
        super(ManPower, self).__init__()
        self.db_hander=DB_handler()
        self.mz_date=MZ_Date()
        self.select_start_date, self.select_end_date=self.mz_date.get_next_month()
        self.standard_workhour_perday = 5*9/7
        self.dirpath = os.path.dirname(__file__)
        self.htmls_path=os.path.join(self.dirpath,'htmls')
        self.project_sankey_path=os.path.join(self.htmls_path,'project_sankey.html')
        self.artist_sankey_path=os.path.join(self.htmls_path,'artist_sankey.html')
        self.project_pie_path=os.path.join(self.htmls_path,'project_pie.html')
        self.artist_pie_path=os.path.join(self.htmls_path,'artist_pie.html')
        self.department_liquid_path=os.path.join(self.htmls_path,'department_liquid.html')
        self.artist_liquid_path=os.path.join(self.htmls_path,'artist_liquid.html')

        self.sicon = QIcon('bu.png')
        self.setWindowIcon(self.sicon)
        self.btn_style='''QPushButton{color:black}
                                  QPushButton:hover{color:#FF7F24}
                                  QPushButton{background-color:#CFCFCF}
                                  QPushButton{border:2px}
                                  QPushButton{border-radius:3px}
                                  QPushButton{padding:1px 1px}'''
        self.check_style = '''QCheckbox:hover{color :##FF7F24}
                              QCheckbox{background-color:#CFCFCF}
                              QCheckbox{padding:1px 1px}'''

        # self.setStyleSheet('QScrollBar{width:5px}')
        self.setWindowTitle("时光坐标项目资源")
        self.main_layout=QHBoxLayout()
        self.hSplitter = QSplitter(Qt.Horizontal)
        # self.left_frame=QFrame()
        self.left_frame=QSplitter(Qt.Vertical)
        self.left_frame.setMinimumWidth(1200)
        self.left_frame.setMinimumHeight(1000)
        # self.left_frame_layout=QVBoxLayout()
        self.project_hsplitter=QSplitter(Qt.Horizontal)
        self.project_sk_browser=QWebEngineView()

        # self.installEventFilter(self)
        # self.project_channel=QWebChannel(self.project_sk_browser.page())
        # self.project_obj=TInteractObj(self)
        # self.project_channel.registerObject("interactObj", self.project_obj)
        # self.project_sk_browser.page().setWebChannel(self.project_channel)
        # self.project_obj.SigReceivedMessFromJS.connect(self.OnReceiveMessageFromJS)


        self.project_pie_browser=QWebEngineView()
        self.project_hsplitter.addWidget(self.project_sk_browser)
        self.project_hsplitter.addWidget(self.project_pie_browser)

        self.artist_hsplitter = QSplitter(Qt.Horizontal)
        self.artist_sk_browser=QWebEngineView()
        self.artist_pie_browser=QWebEngineView()
        self.artist_hsplitter.addWidget(self.artist_sk_browser)
        self.artist_hsplitter.addWidget(self.artist_pie_browser)

        self.left_frame.addWidget(self.project_hsplitter)
        self.left_frame.addWidget(self.artist_hsplitter)


        self.project_pie_browser.settings().setAttribute(QWebEngineSettings.WebAttribute.ShowScrollBars,False)
        self.project_sk_browser.settings().setAttribute(QWebEngineSettings.WebAttribute.ShowScrollBars,False)
        self.artist_sk_browser.settings().setAttribute(QWebEngineSettings.WebAttribute.ShowScrollBars,False)
        self.artist_pie_browser.settings().setAttribute(QWebEngineSettings.WebAttribute.ShowScrollBars,False)




        self.right_frame=QFrame()
        self.rigth_frame_layout=QVBoxLayout()
        self.window_btn_layout=QVBoxLayout()
        self.window_btn_layout.setAlignment(Qt.AlignTop)
        self.window_btn_layout.setSpacing(25)

        self.show_project_info_btn=QPushButton('各项目日历')
        self.show_project_info_btn.setStyleSheet(self.btn_style)
        self.show_project_info_btn.clicked.connect(self._open_project_hot_window)
        self.show_department_info_btn=QPushButton('各部门工时')
        self.show_department_info_btn.setStyleSheet(self.btn_style)
        self.show_department_info_btn.clicked.connect(self._department_statistical_window)
        self.show_liquid_check=QCheckBox('达标率')
        self.show_liquid_check.setStyleSheet("QCheckBox:hover{color:#FF7F24}"
                                   "QCheckBox{border-radius:5px}"
                                   "QCheckBox{background-color:#CFCFCF}")
        self.show_liquid_check.stateChanged.connect(self._show_achievement)
        self.window_btn_layout.addWidget(self.show_project_info_btn)
        self.window_btn_layout.addWidget(self.show_department_info_btn)
        self.window_btn_layout.addWidget(self.show_liquid_check)

        self.date_layout=QVBoxLayout()
        self.date_layout.setAlignment(Qt.AlignTop)
        self.date_layout.setSpacing(15)
        self.start_date_btn=QPushButton(self.select_start_date)
        self.start_date_btn.setStyleSheet(self.btn_style)
        self.start_date_btn.clicked.connect(self._choose_startday)
        self.end_date_btn=QPushButton(self.select_end_date)
        self.end_date_btn.setStyleSheet(self.btn_style)
        self.end_date_btn.clicked.connect(self._choose_endday)
        self.search_btn = QPushButton('生成')
        self.search_btn.setStyleSheet(self.btn_style)
        self.search_btn.clicked.connect(self._create_htmls)
        self.date_layout.addWidget(self.start_date_btn)
        self.date_layout.addWidget(self.end_date_btn)
        self.date_layout.addWidget(self.search_btn)



        self.quick_layout=QVBoxLayout()
        self.quick_layout.setSpacing(20)
        self.last_month_btn=QPushButton('上月')
        self.last_month_btn.setStyleSheet(self.btn_style)
        self.last_month_btn.clicked.connect(self._set_last_month)
        self.this_month_btn=QPushButton('本月')
        self.this_month_btn.setStyleSheet(self.btn_style)
        self.this_month_btn.clicked.connect(self._set_current_month)
        self.next_month_btn=QPushButton('下月')
        self.next_month_btn.setStyleSheet(self.btn_style)
        self.next_month_btn.clicked.connect(self._set_next_month)
        self.last_week_btn=QPushButton('上周')
        self.last_week_btn.setStyleSheet(self.btn_style)
        self.last_week_btn.clicked.connect(self._set_last_week)
        self.this_week_btn=QPushButton('本周')
        self.this_week_btn.setStyleSheet(self.btn_style)
        self.this_week_btn.clicked.connect(self._set_current_week)
        self.next_week_btn=QPushButton('下周')
        self.next_week_btn.setStyleSheet(self.btn_style)
        self.next_week_btn.clicked.connect(self._set_next_week)

        self.quick_layout.addWidget(self.last_month_btn)
        self.quick_layout.addWidget(self.this_month_btn)
        self.quick_layout.addWidget(self.next_month_btn)
        self.quick_layout.addWidget(self.last_week_btn)
        self.quick_layout.addWidget(self.this_week_btn)
        self.quick_layout.addWidget(self.next_week_btn)

        self.help_layout=QVBoxLayout()
        self.help_layout.setAlignment(Qt.AlignBottom)
        self.show_help_btn = QPushButton('帮助说明？')
        self.show_help_btn.setStyleSheet(self.btn_style)
        self.show_help_btn.clicked.connect(self._help)
        self.help_layout.addWidget(self.show_help_btn)
        self.rigth_frame_layout.addLayout(self.window_btn_layout)
        self.rigth_frame_layout.addLayout(self.date_layout)
        self.rigth_frame_layout.addLayout(self.quick_layout)
        self.rigth_frame_layout.addLayout(self.help_layout)
        self.right_frame.setLayout(self.rigth_frame_layout)


        self.hSplitter.addWidget(self.left_frame)
        self.hSplitter.addWidget(self.right_frame)
        self.hSplitter.setSizes([1500, 5])
        self.main_layout.addWidget(self.hSplitter)
        self.setLayout(self.main_layout)

        self._create_htmls()
    def OnReceiveMessageFromJS(self, strParameter):
        print('OnReceiveMessageFromJS()')
        if not strParameter:
            return
        self.mpQtContentTextEdit.appendPlainText(strParameter)
    def _key(self,event):
        print(event)

    def eventFilter(self, QObject, QEvent):
        # print(QObject,QEvent)
        if QObject==self.project_sk_browser:
            print('project_sk_browser event')
            if QEvent.key()==Qt.Key_Enter:
                print('OK')




    def _create_htmls(self):
        """
        生成所有html
        :return:
        """
        start_day = self.start_date_btn.text()
        end_day = self.end_date_btn.text()
        delta = self.mz_date.delta_date(start_day, end_day)
        self.select_start_date = start_day if delta > 0 else end_day
        self.select_end_date = end_day if delta > 0 else start_day


        all_task_info_list = self.db_hander.select_task_in_dates(self.select_start_date, self.select_end_date)
        all_department_per_project_map = self.db_hander.get_all_department_per_project_map(all_task_info_list)
        #sank,pie数据
        nodes, project_linkes,artist_linkes = self.db_hander.get_sankey_data(all_department_per_project_map)
        project_name_workhour_map, artist_count_map=self.db_hander.get_pie_data(all_task_info_list)
        # print('project_name_workhour_map:',project_name_workhour_map)
        # print('artist_count_map:',artist_count_map)

        #liquid 数据
        department_artists_map = self.db_hander.department_artists_map
        all_department_all_workhour, all_department_use_artists=self.db_hander.get_department_all_workhour_artists(all_department_per_project_map)
        all_department_artists_count = self.db_hander.count_dict_value(department_artists_map)
        all_department_use_artists_count=self.db_hander.count_dict_value(all_department_use_artists)
        department_liquid_data=self.db_hander.data_divide_const(all_department_all_workhour,(delta+1)*self.standard_workhour_perday)
        artist_liquid_data=self.db_hander.data_divide_data(all_department_use_artists_count,all_department_artists_count)

        thread_list=[]

        project_sank_Thread=threading.Thread(target=self._create_sankey, args=('项目工时资源流\n(工时)',self.project_sankey_path,nodes, project_linkes))
        thread_list.append(project_sank_Thread)
        artist_sank_Thread=threading.Thread(target=self._create_sankey, args=('项目人力资源流\n(人数)',self.artist_sankey_path,nodes, artist_linkes,'#6A5ACD'))
        thread_list.append(artist_sank_Thread)
        project_pie_Thread=threading.Thread(target=self._create_pie, args=('各项目工时构成',self.project_pie_path,self.select_start_date,self.select_end_date, project_name_workhour_map))
        thread_list.append(project_pie_Thread)
        artist_pie_Thread=threading.Thread(target=self._create_pie, args=("各项目人力构成",self.artist_pie_path,self.select_start_date, self.select_end_date,artist_count_map))
        thread_list.append(artist_pie_Thread)
        department_liquid_Thread=threading.Thread(target=self._create_liquid,args=('各部门工时达标率',self.department_liquid_path,department_liquid_data,"#1E90FF"))
        artist_liquid_Thread=threading.Thread(target=self._create_liquid,args=('各部门人力达标率',self.artist_liquid_path,artist_liquid_data,"#FFDAB9"))
        project_sank_Thread.start()
        artist_sank_Thread.start()
        project_pie_Thread.start()
        artist_pie_Thread.start()
        department_liquid_Thread.start()
        artist_liquid_Thread.start()

        for t in thread_list:   #等所有线程结束
            t.join()


        # self._create_sankey('项目工时资源流\n(工时)',self.project_sankey_path,nodes, project_linkes,artist_linkes)
        # self._create_pie(self.select_start_date, self.select_end_date,project_name_workhour_map,artist_count_map)
        s_path1=self.department_liquid_path if self.show_liquid_check.isChecked() else self.project_pie_path
        s_path2=self.artist_liquid_path if self.show_liquid_check.isChecked() else self.artist_pie_path
        self.show_project_html(self.project_sankey_path,s_path1)
        self.show_artist_html(self.artist_sankey_path,s_path2)

    @info('time')
    def __create_sankey(self,nodes,project_linkes,artist_linkes):
        """
        生成项目、人力资源流
        :param nodes:
        :param project_linkes:
        :param artist_linkes:
        :return:
        """
        project_pic = (Sankey().add(
            '',
            nodes,
            project_linkes,
            pos_right='40%',
            pos_top='15%',
            # pos_left='25%',
            node_width=20,

            layout_iterations=0,
            focus_node_adjacency=True,
            # levels=0,
            itemstyle_opts=opts.ItemStyleOpts(border_width=1, border_color="#aaa"),
            linestyle_opt=opts.LineStyleOpts(opacity=0.3, curve=0.5, color='#EE7621'),
            label_opts=opts.LabelOpts(position='top', vertical_align='middle'),
            node_gap=20,
            node_align='center',
        ).set_global_opts(title_opts=opts.TitleOpts(title='项目工时资源流\n(工时)'))
               )
        project_pic.render(self.project_sankey_path)

        artist_pic = (Sankey().add(
            '',
            nodes,
            artist_linkes,
            pos_right='40%',
            pos_top='15%',
            # pos_left='25%',
            node_width=20,

            layout_iterations=0,
            focus_node_adjacency=True,
            # levels=0,
            itemstyle_opts=opts.ItemStyleOpts(border_width=1, border_color="#aaa"),
            linestyle_opt=opts.LineStyleOpts(opacity=0.3, curve=0.5, color='#6A5ACD'),
            label_opts=opts.LabelOpts(position='top', vertical_align='middle'),
            node_gap=20,
            node_align='center',
        ).set_global_opts(title_opts=opts.TitleOpts(title='项目人力资源流\n(人数)'))
               )
        artist_pic.render(self.artist_sankey_path)

    #@info('time')
    def _create_sankey(self,title,export_path,nodes,project_linkes,color='#EE7621'):
        """
        生成项目、人力资源流
        :param nodes:
        :param project_linkes:
        :param artist_linkes:
        :return:
        """
        project_pic = (Sankey().add(
            '',
            nodes,
            project_linkes,
            pos_right='40%',
            pos_top='15%',
            # pos_left='25%',
            node_width=20,

            layout_iterations=0,
            focus_node_adjacency=True,
            # levels=0,
            itemstyle_opts=opts.ItemStyleOpts(border_width=1, border_color="#aaa"),
            linestyle_opt=opts.LineStyleOpts(opacity=0.3, curve=0.5, color=color),
            label_opts=opts.LabelOpts(position='top', vertical_align='middle'),
            node_gap=20,
            node_align='center',
        ).set_global_opts(title_opts=opts.TitleOpts(title=title))
               )
        project_pic.render(export_path)


    # @info('time')
    def _create_pie(self,title,export_path,start_date,end_date,dataset):
        """
               生成项目、人力资源构成
        :param start_date:
        :param end_date:
        :param workhour_dataset:
        :param artist_dataset:
        :return:
        """

        c = (Pie().
             add('',
                 [[k, v] for k, v in dataset.items()],
                 radius=100,

                 ).set_global_opts(title_opts=opts.TitleOpts(title=title),  #.format(start_date, end_date)
                                   legend_opts=opts.LegendOpts(pos_left="25%"), )
             .set_series_opts(label_opts=opts.LabelOpts(formatter="{b}/{c}"))
             .render(export_path)
             )


    def _create_liquid(self,title,export_path,dataset,lcolor):
        """
        生成占比显示球
        :param title: 标题
        :param export_path: 输出路径
        :param dataset:  数据集
        :param lcolor: 液体颜色
        :return:
        """
        print('_create_liquid:',title,dataset)
        mul = 10
        y_p = 27
        y_p1 = 73
        bias = 5
        f_bias = 3
        f_size = 24

        mp = Liquid(init_opts=opts.InitOpts(width="1400px", height='250px')).add(
            "01美术",
            [dataset.get('01美术',0)],
            center=[f"{mul * 1 + bias}%", f"{y_p}%"],
            color=[lcolor if dataset.get('01美术',0)<=1 else '#FF4500'],
            label_opts=opts.LabelOpts(
                font_size=f_size,
                formatter=JsCode(
                    """function (param) {
                            return (Math.floor(param.value * 10000) / 100) + '%';
                        }"""
                ),
                position="inside",

            ),
        ).add(
            "02模型",
            [dataset.get('02模型',0)],
            center=[f"{mul * 2 + bias}%", f"{y_p}%"],
            color=[lcolor if dataset.get('02模型',0)<=1 else '#FF4500'],
            label_opts=opts.LabelOpts(
                font_size=f_size,
                formatter=JsCode(
                    """function (param) {
                            return (Math.floor(param.value * 10000) / 100) + '%';
                        }"""
                ),
                position="inside",
            ),
        ).add(
            "03跟踪",
            [dataset.get('03跟踪',0)],
            center=[f"{mul * 3 + bias}%", f"{y_p}%"],
            color=[lcolor if dataset.get('03跟踪',0)<=1 else '#FF4500'],
            label_opts=opts.LabelOpts(
                font_size=f_size,
                formatter=JsCode(
                    """function (param) {
                            return (Math.floor(param.value * 10000) / 100) + '%';
                        }"""
                ),
                position="inside",
            ),
        ).add(
            "04动画",
            [dataset.get('04动画',0)],
            center=[f"{mul * 4 + bias}%", f"{y_p}%"],
            color=[lcolor if dataset.get('04动画',0)<=1 else '#FF4500'],
            label_opts=opts.LabelOpts(
                font_size=f_size,
                formatter=JsCode(
                    """function (param) {
                            return (Math.floor(param.value * 10000) / 100) + '%';
                        }"""
                ),
                position="inside",
            ),
        ).add(
            "05场景",
            [dataset.get('05场景',0)],
            center=[f"{mul * 5 + bias}%", f"{y_p}%"],
            color=[lcolor if dataset.get('05场景',0)<=1 else '#FF4500'],
            label_opts=opts.LabelOpts(
                font_size=f_size,
                formatter=JsCode(
                    """function (param) {
                            return (Math.floor(param.value * 10000) / 100) + '%';
                        }"""
                ),
                position="inside",
            ),
        ).add(
            "06灯光",
            [dataset.get('06灯光',0)],
            center=[f"{mul * 6 + bias}%", f"{y_p}%"],
            color=[lcolor if dataset.get('06灯光', 0) <= 1 else '#FF4500'],
            label_opts=opts.LabelOpts(
                font_size=f_size,
                formatter=JsCode(
                    """function (param) {
                            return (Math.floor(param.value * 10000) / 100) + '%';
                        }"""
                ),
                position="inside",
            ),
        ).add(
            "07特效一",
            [dataset.get('07特效一',0)],
            center=[f"{mul * 7 + bias}%", f"{y_p}%"],
            color=[lcolor if dataset.get('07特效一', 0) <= 1 else '#FF4500'],
            label_opts=opts.LabelOpts(
                font_size=f_size,
                formatter=JsCode(
                    """function (param) {
                            return (Math.floor(param.value * 10000) / 100) + '%';
                        }"""
                ),
                position="inside",
            ),
        ).add(
            "07特效二",
            [dataset.get('07特效二',0)],
            center=[f"{mul * 1}%", f"{y_p1}%"],
            color=[lcolor if dataset.get('07特效二', 0) <= 1 else '#FF4500'],
            label_opts=opts.LabelOpts(
                font_size=f_size,
                formatter=JsCode(
                    """function (param) {
                            return (Math.floor(param.value * 10000) / 100) + '%';
                        }"""
                ),
                position="inside",
            ),
        ).add(
            "08合成一",
            [dataset.get('08合成一',0)],
            center=[f"{mul * 2}%", f"{y_p1}%"],
            color=[lcolor if dataset.get('08合成一', 0) <= 1 else '#FF4500'],
            label_opts=opts.LabelOpts(
                font_size=f_size,
                formatter=JsCode(
                    """function (param) {
                            return (Math.floor(param.value * 10000) / 100) + '%';
                        }"""
                ),
                position="inside",
            ),
        ).add(
            "08合成二",
            [dataset.get('08合成二',0)],
            center=[f"{mul * 3}%", f"{y_p1}%"],
            color=[lcolor if dataset.get('08合成二', 0) <= 1 else '#FF4500'],
            label_opts=opts.LabelOpts(
                font_size=f_size,
                formatter=JsCode(
                    """function (param) {
                            return (Math.floor(param.value * 10000) / 100) + '%';
                        }"""
                ),
                position="inside",
            ),
        ).add(
            "09包装",
            [dataset.get('09包装',0)],
            center=[f"{mul * 4}%", f"{y_p1}%"],
            color=[lcolor if dataset.get('09包装', 0) <= 1 else '#FF4500'],
            label_opts=opts.LabelOpts(
                font_size=f_size,
                formatter=JsCode(
                    """function (param) {
                            return (Math.floor(param.value * 10000) / 100) + '%';
                        }"""
                ),
                position="inside",
            ),
        ).add(
            "10剪辑",
            [dataset.get('10剪辑',0)],
            center=[f"{mul * 5}%", f"{y_p1}%"],
            color=[lcolor if dataset.get('10剪辑', 0) <= 1 else '#FF4500'],
            label_opts=opts.LabelOpts(
                font_size=f_size,
                formatter=JsCode(
                    """function (param) {
                            return (Math.floor(param.value * 10000) / 100) + '%';
                        }"""
                ),
                position="inside",
            ),
        ).add(
            "11调色",
            [dataset.get('11调色',0)],
            center=[f"{mul * 6}%", f"{y_p1}%"],
            color=[lcolor if dataset.get('11调色', 0) <= 1 else '#FF4500'],
            label_opts=opts.LabelOpts(
                font_size=f_size,
                formatter=JsCode(
                    """function (param) {
                            return (Math.floor(param.value * 10000) / 100) + '%';
                        }"""
                ),
                position="inside",
            ),
        ).add(
            "12TD",
            [dataset.get('12TD',0)],
            center=[f"{mul * 7}%", f"{y_p1}%"],
            # color= ["#FF0000", "#FF4500", "#FF7F00", "#ffa345"],
            # color= ["#FF7F00", "#ffa345"],
            # color= ["#1E90FF", "#ffa345"],
            color=[lcolor if dataset.get('12TD', 0) <= 1 else '#FF4500'],
            # color = "#FF0000",
            # color = "#FF7F00",
            # outline_itemstyle_opts={'color':"#FF7F00"},
            label_opts=opts.LabelOpts(
                font_size=f_size,
                # color='#fafafa',
                formatter=JsCode(
                    """function (param) {
                            return (Math.floor(param.value * 10000) / 100) + '%';
                        }"""
                ),
                position="inside",
            )
        ).set_global_opts(title_opts=opts.TitleOpts(title=title),
                          graphic_opts=[opts.GraphicText(
                              graphic_item=opts.GraphicItem(
                                  left=f"{mul * 1 + f_bias}%",
                                  top=f"{y_p - bias * 3}%",
                                  z=100, ),
                              # color='#FF7F00',
                              graphic_textstyle_opts=opts.GraphicTextStyleOpts(
                                  # 可以通过jsCode添加js代码，也可以直接用字符串
                                  text='01美术',
                                  font="14px ",
                                  #  color='#FF7F00',
                                  graphic_basicstyle_opts=opts.GraphicBasicStyleOpts(
                                      fill="#333")
                              )
                          ),
                              opts.GraphicText(
                                  graphic_item=opts.GraphicItem(
                                      left=f"{mul * 2 + f_bias}%",
                                      top=f"{y_p - bias * 3}%",
                                      z=100, ),
                                  # color='#FF7F00',
                                  graphic_textstyle_opts=opts.GraphicTextStyleOpts(
                                      # 可以通过jsCode添加js代码，也可以直接用字符串
                                      text='02模型',
                                      font="14px",
                                      #  color='#FF7F00',
                                      graphic_basicstyle_opts=opts.GraphicBasicStyleOpts(
                                          fill="#333")
                                  )
                              ),
                              opts.GraphicText(
                                  graphic_item=opts.GraphicItem(
                                      left=f"{mul * 3 + f_bias}%",
                                      top=f"{y_p - bias * 3}%",
                                      z=100, ),
                                  # color='#FF7F00',
                                  graphic_textstyle_opts=opts.GraphicTextStyleOpts(
                                      # 可以通过jsCode添加js代码，也可以直接用字符串
                                      text='03跟踪',
                                      font="14px",
                                      #  color='#FF7F00',
                                      graphic_basicstyle_opts=opts.GraphicBasicStyleOpts(
                                          fill="#333")
                                  )
                              ),

                              opts.GraphicText(
                                  graphic_item=opts.GraphicItem(
                                      left=f"{mul * 4 + f_bias}%",
                                      top=f"{y_p - bias * 3}%",
                                      z=100, ),
                                  # color='#FF7F00',
                                  graphic_textstyle_opts=opts.GraphicTextStyleOpts(
                                      # 可以通过jsCode添加js代码，也可以直接用字符串
                                      text='04动画',
                                      font="14px",
                                      #  color='#FF7F00',
                                      graphic_basicstyle_opts=opts.GraphicBasicStyleOpts(
                                          fill="#333")
                                  )
                              ),
                              opts.GraphicText(
                                  graphic_item=opts.GraphicItem(
                                      left=f"{mul * 5 + f_bias}%",
                                      top=f"{y_p - bias * 3}%",
                                      z=100, ),
                                  # color='#FF7F00',
                                  graphic_textstyle_opts=opts.GraphicTextStyleOpts(
                                      # 可以通过jsCode添加js代码，也可以直接用字符串
                                      text='05场景',
                                      font="14px",
                                      #  color='#FF7F00',
                                      graphic_basicstyle_opts=opts.GraphicBasicStyleOpts(
                                          fill="#333")
                                  )
                              ),
                              opts.GraphicText(
                                  graphic_item=opts.GraphicItem(
                                      left=f"{mul * 6 + f_bias}%",
                                      top=f"{y_p - bias * 3}%",
                                      z=100, ),
                                  # color='#FF7F00',
                                  graphic_textstyle_opts=opts.GraphicTextStyleOpts(
                                      # 可以通过jsCode添加js代码，也可以直接用字符串
                                      text='06灯光',
                                      font="14px",
                                      #  color='#FF7F00',
                                      graphic_basicstyle_opts=opts.GraphicBasicStyleOpts(
                                          fill="#333")
                                  )
                              ),
                              opts.GraphicText(
                                  graphic_item=opts.GraphicItem(
                                      left=f"{mul * 7 + f_bias}%",
                                      top=f"{y_p - bias * 3}%",
                                      z=100, ),
                                  # color='#FF7F00',
                                  graphic_textstyle_opts=opts.GraphicTextStyleOpts(
                                      # 可以通过jsCode添加js代码，也可以直接用字符串
                                      text='07特效一',
                                      font="14px",
                                      #  color='#FF7F00',
                                      graphic_basicstyle_opts=opts.GraphicBasicStyleOpts(
                                          fill="#333")
                                  )
                              ),
                              opts.GraphicText(
                                  graphic_item=opts.GraphicItem(
                                      left=f"{mul * 0.5 + f_bias}%",
                                      top=f"{y_p1 - bias * 3}%",
                                      z=100, ),
                                  # color='#FF7F00',
                                  graphic_textstyle_opts=opts.GraphicTextStyleOpts(
                                      # 可以通过jsCode添加js代码，也可以直接用字符串
                                      text='07特效二',
                                      font="14px",
                                      #  color='#FF7F00',
                                      graphic_basicstyle_opts=opts.GraphicBasicStyleOpts(
                                          fill="#333")
                                  )
                              ),
                              opts.GraphicText(
                                  graphic_item=opts.GraphicItem(
                                      left=f"{mul * 1.5 + f_bias}%",
                                      top=f"{y_p1 - bias * 3}%",
                                      z=100, ),
                                  # color='#FF7F00',
                                  graphic_textstyle_opts=opts.GraphicTextStyleOpts(
                                      # 可以通过jsCode添加js代码，也可以直接用字符串
                                      text='08合成一',
                                      font="14px",
                                      #  color='#FF7F00',
                                      graphic_basicstyle_opts=opts.GraphicBasicStyleOpts(
                                          fill="#333")
                                  )
                              ),

                              opts.GraphicText(
                                  graphic_item=opts.GraphicItem(
                                      left=f"{mul * 2.5 + f_bias}%",
                                      top=f"{y_p1 - bias * 3}%",
                                      z=100, ),
                                  # color='#FF7F00',
                                  graphic_textstyle_opts=opts.GraphicTextStyleOpts(
                                      # 可以通过jsCode添加js代码，也可以直接用字符串
                                      text='08合成二',
                                      font="14px",
                                      #  color='#FF7F00',
                                      graphic_basicstyle_opts=opts.GraphicBasicStyleOpts(
                                          fill="#333")
                                  )
                              ),

                              opts.GraphicText(
                                  graphic_item=opts.GraphicItem(
                                      left=f"{mul * 3.5 + f_bias}%",
                                      top=f"{y_p1 - bias * 3}%",
                                      z=100, ),
                                  # color='#FF7F00',
                                  graphic_textstyle_opts=opts.GraphicTextStyleOpts(
                                      # 可以通过jsCode添加js代码，也可以直接用字符串
                                      text='09包装',
                                      font="14px",
                                      #  color='#FF7F00',
                                      graphic_basicstyle_opts=opts.GraphicBasicStyleOpts(
                                          fill="#333")
                                  )
                              ),
                              opts.GraphicText(
                                  graphic_item=opts.GraphicItem(
                                      left=f"{mul * 4.5 + f_bias}%",
                                      top=f"{y_p1 - bias * 3}%",
                                      z=100, ),
                                  graphic_textstyle_opts=opts.GraphicTextStyleOpts(
                                      # 可以通过jsCode添加js代码，也可以直接用字符串
                                      text='10剪辑',
                                      font="14px",
                                      graphic_basicstyle_opts=opts.GraphicBasicStyleOpts(
                                          fill="#333")
                                  )
                              ),
                              opts.GraphicText(
                                  graphic_item=opts.GraphicItem(
                                      left=f"{mul * 5.5 + f_bias}%",
                                      top=f"{y_p1 - bias * 3}%",
                                      z=100, ),
                                  graphic_textstyle_opts=opts.GraphicTextStyleOpts(
                                      # 可以通过jsCode添加js代码，也可以直接用字符串
                                      text='11调色',
                                      font="14px",
                                      graphic_basicstyle_opts=opts.GraphicBasicStyleOpts(
                                          fill="#333")
                                  )
                              ),
                              opts.GraphicText(
                                  graphic_item=opts.GraphicItem(
                                      left=f"{mul * 6.5 + f_bias}%",
                                      top=f"{y_p1 - bias * 3}%",
                                      z=100, ),
                                  graphic_textstyle_opts=opts.GraphicTextStyleOpts(
                                      # 可以通过jsCode添加js代码，也可以直接用字符串
                                      text='12TD',
                                      font="14px",
                                      graphic_basicstyle_opts=opts.GraphicBasicStyleOpts(
                                          fill="#333")
                                  )
                              ),

                          ]
                          )

        mp.render(export_path)





    #日期选择
    def _choose_startday(self):
        self.calender=Calendar()
        self.calender.dateSignal.connect(self._set_startday)
        self.calender.show()

    def _set_startday(self,date):
        self.select_start_date=date
        self.start_date_btn.setText(date)

    def _choose_endday(self):
        self.calender=Calendar()
        self.calender.dateSignal.connect(self._set_endday)
        self.calender.show()

    def _set_endday(self,date):
        self.select_end_date=date
        self.end_date_btn.setText(date)


    #设置日期
    def _set_last_week(self):
        self.select_start_date,self.select_end_date=self.mz_date.get_last_week()
        self.start_date_btn.setText(self.select_start_date)
        self.end_date_btn.setText(self.select_end_date)
        self._create_htmls()

    def _set_current_week(self):
        self.select_start_date,self.select_end_date=self.mz_date.get_current_week()
        self.start_date_btn.setText(self.select_start_date)
        self.end_date_btn.setText(self.select_end_date)
        self._create_htmls()

    def _set_next_week(self):
        self.select_start_date,self.select_end_date=self.mz_date.get_next_week()
        self.start_date_btn.setText(self.select_start_date)
        self.end_date_btn.setText(self.select_end_date)
        self._create_htmls()


    def _set_last_month(self):
        self.select_start_date,self.select_end_date=self.mz_date.get_last_month()
        self.start_date_btn.setText(self.select_start_date)
        self.end_date_btn.setText(self.select_end_date)
        self._create_htmls()

    def _set_current_month(self):
        self.select_start_date,self.select_end_date=self.mz_date.get_current_month()
        self.start_date_btn.setText(self.select_start_date)
        self.end_date_btn.setText(self.select_end_date)
        self._create_htmls()

    def _set_next_month(self):
        self.select_start_date,self.select_end_date=self.mz_date.get_next_month()
        self.start_date_btn.setText(self.select_start_date)
        self.end_date_btn.setText(self.select_end_date)
        self._create_htmls()





    def show_project_html(self,sk_html_path,pie_html_path):
        """
         展示html内容
        :param sk_html_path:
        :param pie_html_path:
        :return:
        """
        self.project_sk_browser.load(QUrl.fromLocalFile(sk_html_path))
        self.project_pie_browser.load(QUrl.fromLocalFile(pie_html_path))

    def show_artist_html(self,sk_html_path,pie_html_path):
        """
        展示人员分配
        :param sk_html_path:
        :param pie_html_path:
        :return:
        """
        self.artist_sk_browser.load(QUrl.fromLocalFile(sk_html_path))
        self.artist_pie_browser.load(QUrl.fromLocalFile(pie_html_path))

    def _open_project_hot_window(self):
        """
        打开prject_hot窗口
        :return:
        """
        self.hot_window=ProjectHotWindow(self.select_start_date,self.select_end_date)
        self.hot_window.show()

    def _department_statistical_window(self):
        """
        打开部门统计面板
        :return:
        """
        self.dewindow=DepartmentStatisticalWindow(self.select_start_date,self.select_end_date)
        self.dewindow.show()

    def _show_achievement(self,status):
        if status==Qt.Checked:
            print('显示达标率')
            self.project_pie_browser.load(QUrl.fromLocalFile(self.department_liquid_path))
            self.artist_pie_browser.load(QUrl.fromLocalFile(self.artist_liquid_path))
        else:
            self.project_pie_browser.load(QUrl.fromLocalFile(self.project_pie_path))
            self.artist_pie_browser.load(QUrl.fromLocalFile(self.artist_pie_path))
            print('显示饼图')


    def _help(self):
        """
        帮助说明
        :return:
        """
        QMessageBox.about(self,"帮助说明","操作方式:\n\n"
                                      "选择对应的时间段->生成。 点击上月、本月等按钮快捷方式可以直接生成。生成时请稍等2秒\n\n"
                                      "工时资源流：左边节点为部门，右边节点为该时间段安排的项目，鼠标放在各节点上可显示总量。放在线上可以显示分量"
                                      "可查看该时间段内，所有已安排项目的所有部门在各项目的总工时资源流。\n\n"
                                      "人力资源流: 左边节点为部门，右边节点为该时间段安排的人力，\n"
                                      "查看该时间段内，所有已安排项目所有部门在各项目的人力分配。\n\n"
                                      "工时构成：该时间段内，各个项目的总工时构成,点击最上面项目可以过滤显示\n\n"
                                      "人力构成: 该时间段内，各个项目的总人力构成,点击最上面项目可以过滤显示\n\n"
                                      "项目日历：打开各项目的每日工时图,可以查看各部门各项目每天的安排工时分配\n\n"
                                      "部门工时：显示部门各人员安排工时与自填工时")


if __name__ == '__main__':
    app=QApplication(sys.argv)
    m=ManPower()
    # sk_html_path=r'F:/PycharmOut/SanKey/test.html'
    # sk_aritist_html_path=r'F:/PycharmOut/SanKey/test_aritist.html'
    # one_pie_path=r'F:/PycharmOut/SanKey/one_pie.html'
    # one_pie_artist_path=r'F:/PycharmOut/SanKey/one_pie_artist.html'
    # m.show_project_html(sk_html_path,one_pie_path)
    # m.show_artist_html(sk_aritist_html_path,one_pie_artist_path)
    m.show()
    sys.exit(app.exec_())
